using System;
using System.Collections.Generic;
using System.Text;

namespace FE
{
    public class Unit
    {
        public enum UnitType
        {
            Infantry,
            Cavalier,
            Flier
        }

        protected string name;

        protected UnitType type;

        protected Holdable[] Inventory = new Holdable[5];

        protected Stat HitPoint, Strength, Magic, Skill, Speed, Luck, Defense, Resistance, Movement, Constitution;

        public int MovementValue
        {
            get { return Movement.Value; }
        }

        public int HitPointValue
        {
            get { return HitPoint.Value; }
        }

        public string Name
        {
            get { return name; }
            set { name = value; }
        }

        public UnitType Type
        {
            get { return type; }
        }

        //Damage = Power + Effective Weapon Might - Target Effective Defence + Bonuses
        //( 0-5 Def from supports)
        public int GetDamage (Unit target)
        {            
            return GetPower() + GetEquippedWeapon().GetEffectiveMight(target.GetEquippedWeapon()) - target.GetDefense();
        }
        public Weapon GetEquippedWeapon ()
        {
            return Inventory[0] as Weapon;
        }
        public int GetPower ()
        {            
            if (GetEquippedWeapon().UsesStrength())
                return Strength.Value;
            else
                return Magic.Value;
        }
        //Effective defence = Def/Res + Bonuses (0-5 Def supports, 0-2 from terrain)
        public int GetDefense ()
        {
            return (int) ((double)Defense.Value/(double)Resistance.Value);
        }
        //Hit rate = 2* Skill + 0.5* Luck - Target avoid + weapon hit rate + Bonuses 
        //(+5% from S rank in weapon level and 0-25% depending on supports)
        public int GetHitRate (Unit target)
        {            
            return 2 * Skill.Value + (int)(0.5 * Luck.Value) - target.GetAvoid() + GetEquippedWeapon().GetHitRate(target.GetEquippedWeapon());
        }
        //Avoid = 2* attack speed + luck + bonuses (0-25% from supports, 0-40% from 
        //different terrain)
        public int GetAvoid ()
        {
            return 2*GetAttackSpeed() + Luck.Value;
        }
        public bool CanDoubleAttack (Unit target)
        {
            return Speed.Value > target.Speed.Value + 4;
        }
        //Attack speed:
        //Weapon Wt. > Con = Speed + (Con - Weapon Weight)
        //Weapon Wt. < Con = Speed
        //Weapon Wt. = Con, = Speed
        public int GetAttackSpeed ()
        {            
            if (GetEquippedWeapon().Weight <= Constitution.Value)
                return Speed.Value;
            else
                return Speed.Value + (Constitution.Value - GetEquippedWeapon().Weight);
        }

        //Critical rate = Weapon critical + 0.5*skill - target critical evade + bonuses
        //(+5% if S in weapon, +15% for swordmasters/berserkers, 0-25% supports)
        public int GetCriticalChance (Unit target)
        {
            return GetEquippedWeapon().Critical + (int)(0.5 * Skill.Value) - target.GetCriticalEvade();
        }
        //Critical evade = Luck + Bonuses (0-25% supports)
        public int GetCriticalEvade ()
        {
            return Luck.Value;
        }
    }

    public class UnitStatus
    {
        public Unit unit;
        public int health;
        //statuses
        public bool hasTurn = true;
        public UnitStatus(Unit unit)
        {
            this.unit = unit;
            this.health = unit.HitPointValue;
        }

        public void DoDamage(int damage)
        {
            health -= damage;
        }
        public bool IsDead
        {
            get { return health <= 0; }
        }
    }

}
